using Microsoft.Xna.Framework;
using Rocuna.GameEngine.Constants;
using Rocuna.GameEngine.State;
using Rocuna.GameEngine.State.Screens;
using Rocuna.Graphics;
using Rocuna.HID;

namespace Rocuna.GameEngine
{
    /// <summary>
    /// Bootstrapper to enable overriding basic Implementation of managers.
    /// </summary>
    public abstract class RocunaBootstrapper
    {
        #region Properties

        protected RocunaGame Game { get; set; }

        #endregion


        #region Creation methods

        /// <summary>
        /// Creates the input manager.
        /// </summary>
        /// <returns></returns>
        public virtual InputManager CreateInputManager()
        {
            return new InputManager();
        }

        /// <summary>
        /// Creates the graphic manager.
        /// </summary>
        /// <returns></returns>
        public virtual GraphicManager CreateGraphicManager(Game game)
        {
            return new GraphicManager(game);
        }

        /// <summary>
        /// Creates the screen manager.
        /// </summary>
        /// <returns></returns>
        public virtual ScreenManager CreateScreenManager()
        {
            return new ScreenManager();
        }

        #endregion

        #region Run methods

        /// <summary>
        /// Runs this bootstrapper.
        /// </summary>
        public virtual void Run()
        {
            var game = ConfigureGame();
            CreationLogic(game);
        }

        /// <summary>
        /// Runs the bootstrapper with specified game instance.
        /// </summary>
        /// <param name="game">The game instance.</param>
        public virtual void Run(RocunaGame game)
        {
            CreationLogic(game);
        }

        #endregion

        #region Protected helpers

        /// <summary>
        /// Logic for creation and initialization of the Engine.
        /// </summary>
        /// <param name="game">The game.</param>
        protected void CreationLogic(RocunaGame game)
        {
            Game = game;

            // Graphic prepare operation. 
            Game.SetGraphicManager(CreateGraphicManager(game));

            // Input prepare operations
            Game.SetInputManager(CreateInputManager());
            RegisterDevices();

            //Game states and screen operations.
            Game.SetScreenManager(CreateScreenManager());
            RegisterScreens();
        }

        #endregion

        #region Configure methods

        /// <summary>
        /// Configures the game refer to your game instance.
        /// </summary>
        /// <returns></returns>
        public abstract RocunaGame ConfigureGame();

        /// <summary>
        /// Registers the input devices.
        /// </summary>
        public virtual void RegisterDevices()
        {

        }

        /// <summary>
        /// Registers the screens.
        /// </summary>
        public virtual void RegisterScreens()
        {
        }

        #endregion


    }
}